<?php

namespace App\Http\Controllers\Mp;

use App\Contract\ContractStatus;
use App\Http\Controllers\Controller;
use App\Model\Contract;
use App\Model\Fdd;
use App\Service\Fdd\FddInterface;
use App\Utils\Result;
use App\Utils\Utils;
use Carbon\Carbon;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Log;

class FddController extends Controller
{
    protected FddInterface $fdd;

    public function __construct(FddInterface $fdd)
    {
        $this->fdd = $fdd;
    }

    public function getInfo(): \Illuminate\Http\JsonResponse
    {
        $user = $this->getUser();
        $fdd = $user->fdd()->first();
        if (!$fdd) {
            $fdd = new Fdd();
            $fdd->user_id = $user->id;
            $fdd->mobile = $user->mobile;
            $fdd->user_name = '';
            $fdd->ident_no = '';
            $fdd->ident_type = 'id_card';
            $fdd->is_corp = 0;
            $fdd->status = 1;
            $fdd->save();
        }
        if ($fdd->user_name && $fdd->status < 2) {
            try {
                if (!$fdd->is_corp) {
                    $result = $this->fdd->getUserInfo($fdd->user_id);
                    $fdd->open_user_id = $result['openUserId'];
                    $fdd->status = $result['identStatus'] == 'unidentified' ? 1 : 2;
                    $fdd->save();
                } else {
                    $result = $this->fdd->getCorpInfo($fdd->user_id);
                    $fdd->open_user_id = $result['openCorpId'];
                    $fdd->status = $result['identStatus'] == 'unidentified' ? 1 : 2;
                    $fdd->save();
                }
            } catch (\Exception $exception) {
                //
            }
        }

        return Result::success($fdd);
    }

    public function updateInfo(Request $request): \Illuminate\Http\JsonResponse
    {
        $data = $request->only([
            'is_corp',
            'mobile',
            'user_name',
            'ident_type',
            'ident_no',
        ]);

        $user = $this->getUser();
        $fdd = $user->fdd()->first();
        if ($fdd) {
            $fdd->fill($data);
            $fdd->save();
        } else {
            $fdd = new Fdd();
            $fdd->user_id = $user->id;
            $fdd->fill($data);
            $fdd->save();
        }
        if ($user->business) {
            $user->business->name = $fdd->user_name;
            $user->business->save();
        }

        return Result::success($fdd);
    }

    /**
     * 获取个人认证授权链接
     * @param Request $request
     * @return \Illuminate\Http\JsonResponse
     */
    public function getAuthUrl(Request $request): \Illuminate\Http\JsonResponse
    {
        $user = $this->getUser();
        $fdd = $user->fdd()->first();
        if ($fdd->is_corp) {
            $bizContent = [
                'clientCorpId' => $fdd->user_id,
                'clientUserId' => $fdd->user_id,
                'accountName' => $fdd->mobile,
                'corpIdentInfo' => [
                    'corpName' => $fdd->user_name,
                    'corpIdentType' => $fdd->ident_type,
                    'corpIdentNo' => $fdd->ident_no,
                ],
                'authScopes' =>  ['ident_info', 'seal_info', 'organization', 'template', 'signtask_init', 'signtask_info', 'signtask_file'],
                'redirectUrl' => '/pages/my/fdd/fdd'
            ];
        } else {
            $bizContent = [
                'clientUserId' => $fdd->user_id,
                'accountName' => $fdd->mobile,
                'userIdentInfo' => [
                    'userName' => $fdd->user_name,
                    'userIdentType' => $fdd->ident_type,
                    'userIdentNo' => $fdd->ident_no,
                    'identMethod' => ['mobile']
                ],
                'authScopes' =>  ['ident_info', 'seal_info', 'signtask_init', 'signtask_info', 'signtask_file'],
                'redirectUrl' => '/pages/my/fdd/fdd',
                'freeSignInfo' => [
                    'businessId' => env('FDD_BUSINESS_ID')
                ]
            ];
        }

        $result = $this->fdd->getUserAuthUrl($bizContent);

        return Result::success($result);
    }

    public function userUnbind()
    {
        $user = $this->getUser();
        $fdd = $user->fdd()->first();
        $this->fdd->userUnbind($fdd->open_user_id);
        $fdd->open_user_id = null;
        $fdd->status = 1;
        $fdd->save();
        return Result::success();
    }

    public function getFreeSignUrl(Request $request)
    {
        $user = $this->getUser();
        $fdd = $user->fdd()->first();
        if ($fdd->is_corp) {
            $sealResult = $this->fdd->getCorpSealList([
                'openCorpId' => $fdd->open_user_id,
            ]);
            $result = $this->fdd->getCorpFreeSignUrl([
                'openCorpId' => $fdd->open_user_id,
                'sealIds' => [$sealResult['sealInfos'][0]['sealId']],
                'businessId' => env('FDD_BUSINESS_ID', '2f5180c6bde474ea9e6f0f4a6829946f'),
                //'redirectUrl' => '/pages/my/fdd/fdd'
            ]);
        } else {
            $sealResult = $this->fdd->getPersonalSealList([
                'openUserId' => $fdd->open_user_id,
            ]);
            $result = $this->fdd->getPersonalFreeSignUrl([
                'openUserId' => $fdd->open_user_id,
                'sealIds' => [$sealResult['sealInfos'][0]['sealId']],
                'businessId' => env('FDD_BUSINESS_ID', '2f5180c6bde474ea9e6f0f4a6829946f'),
                //'redirectUrl' => '/pages/my/fdd/fdd'
            ]);
        }

        return Result::success($result);
    }

    /**
     * 获取签署任务模板
     * @return \Illuminate\Http\JsonResponse
     */
    public function getSignTemplateList(): \Illuminate\Http\JsonResponse
    {
        $data = $this->fdd->getSignTemplateList([
            "listPageNo" => 1,
            "listPageSize" => 100
        ]);
        return Result::success($data);
    }

//    public function getSignTemplateDetail(Request $request): \Illuminate\Http\JsonResponse
//    {
//        $id = $request->input('id');
//        $data = $this->fdd->getSignTemplateDetail($id);
//        return Result::success($data);
//    }

    public function createSignTask(Request $request): \Illuminate\Http\JsonResponse
    {
        $contractId = $request->input('contractId');
        $contract = Contract::query()->with(['business', 'house', 'contractRent', 'masterTenant'])->find($contractId);
        if (!$contract) {
            return Result::error(404, '合同不存在');
        }
        $user = $this->getUser();
        //$fdd = $user->fdd()->first();
        $bank = $user->bank;
        if (!$bank) {
            return Result::error(401, '请先绑卡后再操作');
        }

        $data = [
            'initiator' => [
                'idType' => 'corp',
                'openId' => env('FDD_OPENID', 'fb17eff87ee149a6889edfb56572af74'),
            ],
            'signTaskSubject' => $contract->house->estate_name . $contract->house->name . '-租房合同' . date('Ymd'),
            'signDocType' => 'contract',
            'signTemplateId' => $contract->template_id,
            'expiresTime' => Carbon::createFromFormat('Y-m-d', $contract->expired_at)->timestamp * 1000,
            'dueDate' => Carbon::createFromFormat('Y-m-d', $contract->expired_at)->addHours(23)->timestamp * 1000,
            'autoFinish' => true,
            //'businessId' => env('FDD_BUSINESS_ID', '2f5180c6bde474ea9e6f0f4a6829946f'),
            'transReferenceId' => $contract->sn,
            'actors' => [
                [
                    'actor' => [
                        'actorId' => '房东',
                        'actorType' => 'person',
                        'actorName' => $bank->card_name,
                        //'actorOpenId' => $fdd->open_user_id,
                        'permissions' => ['sign'],
                        'accountName' => $user->mobile
                    ],
                    'signConfigInfo' => [
                        'freeLogin' => true,
                        'identifiedView' => false,
                        //'requestVerifyFree' => true
                    ]
                ],
                [
                    'actor' => [
                        'actorId' => '房客',
                        'actorType' => $contract->masterTenant->type == 1 ? 'person' : 'corp',
                        'actorName' => $contract->masterTenant->name,
                        'identNameForMatch' => $contract->masterTenant->name,
                        'permissions' => ['sign'],
                        'accountName' => $contract->masterTenant->mobile
                    ],
                    'signConfigInfo' => [
                        'freeLogin' => true,
                        'identifiedView' => false,
                    ]
                ]
            ]
        ];

//        if ($contract->sign_task_id) {
//            $this->fdd->signTaskDelete($contract->sign_task_id);
//        }

        Log::notice('createSignTaskWithTemplate', $data);

        $task = $this->fdd->createSignTaskWithTemplate($data);
        $contract->status = ContractStatus::DAIQIANYUE;
        $contract->sign_task_id = $task['signTaskId'];
        $contract->save();

        // 填写字段
        $this->fillFields($contract, $bank);

        // start
        $this->fdd->signTaskStart($contract->sign_task_id);

        // 定稿
        //$this->fdd->signTaskFinalize($contract->sign_task_id);

        return Result::success();
    }

    public function getSignTaskUrl(Request $request, $id)
    {
        $actorId = $request->input('actorId', '房客');
        $contract = Contract::query()->find($id);
        $weappUrl = $actorId == '房东' ? '/pages/contract/createResult/createResult?id=' . $id : '/pages/contract/detail/detail?id=' . $id;

        // 获取签署链接
        $result = $this->fdd->signTaskGetUrl([
            'signTaskId' => $contract->sign_task_id,
            'actorId' => $actorId ?? '房客',
            'redirectMiniAppUrl' => urlencode($weappUrl)
        ]);

        return Result::success($result);
    }

    public function getSignTaskDownloadUrl(Request $request, $id)
    {
        $user = $this->getUser();
        $fdd = $user->fdd()->first();
        $contract = Contract::query()->find($id);
        // 获取签署链接
        $result = $this->fdd->signTaskGetDownloadUrl([
            'ownerId' => [
                'idType' => 'corp',
                'openId' => env('FDD_OPENID', 'fb17eff87ee149a6889edfb56572af74'),
            ],
            'signTaskId' => $contract->sign_task_id,
        ]);

        return Result::success($result);
    }

    public function getSignTaskPreviewUrl($id)
    {
        $contract = Contract::query()->find($id);
        // 获取签署preview链接
        $result = $this->fdd->signTaskGetPreviewUrl([
            'signTaskId' => $contract->sign_task_id
        ]);

        return Result::success($result);
    }

    public function fillFields($contract, $bank)
    {
        $templateDetail = $this->fdd->getSignTemplateDetail($contract->template_id);
        $docFieldValues = [];
        $doc = $templateDetail['docs'][0];
        $contractFields = [
            'sn' => $contract->sn,
            'business_name' => $bank->card_name,
            'business_ident_type' => '身份证',
            'business_ident_no' => $bank->cert_id,
            'tenant_name' => $contract->masterTenant->name,
            'tenant_ident_type' => $contract->masterTenant->type == 1 ? '身份证' : '营业执照',
            'tenant_ident_no' => $contract->masterTenant->type == 1 ? $contract->masterTenant->id_no : $contract->masterTenant->credit_no,
            'tenant_mobile' => $contract->masterTenant->mobile,
            'house_name' => $contract->house->estate_name . $contract->house->name,
            'house_size' => $contract->house->size ?: '无',
            'contract_start_date' => $contract->start_at,
            'contract_end_date' => $contract->expired_at,
            'contract_month_num' => $contract->contractRent->month_num,
            'contract_start_date2' => $contract->start_at,
            'rent_up' => Utils::toCnAmount($contract->contractRent->amount),
            'rent' => $contract->contractRent->amount,
            'rent_total_up' => Utils::toCnAmount($contract->contractRent->amount * $contract->contractRent->month_num),
            'tent_total' => $contract->contractRent->amount * $contract->contractRent->month_num,
            'rent_num_name' => $contract->contractRent->rent_num_name,
            'deposit' => $contract->contractRent->deposit ? : '无',
            'remark' => $contract->remark,
            'deposit_up' => $contract->contractRent->deposit ? Utils::toCnAmount($contract->contractRent->deposit) : '无'
        ];
        foreach ($doc['docFields'] as $field) {
            //$docFieldValues
            if (isset($contractFields[$field['fieldId']])) {
                $docFieldValues[] = [
                    'docId' => $doc['docId'],
                    'fieldId' => $field['fieldId'],
                    'fieldValue' => $contractFields[$field['fieldId']],
                ];
            }
        }
        Log::info('docFieldValues', [$docFieldValues, $contractFields, $templateDetail]);
        $this->fdd->signTaskFillValues([
            'signTaskId' => $contract->sign_task_id,
            'docFieldValues' => $docFieldValues
        ]);
    }
}
